using System;
using System.Collections.Generic;
using System.Text;
using System.Web.UI;
using DotSVN.Common;
using DotSVN.Common.Entities;
using DotSVN.Server.RepositoryAccess;

namespace DotSVN.WebSample
{
    public partial class Browse : Page
    {
        private const string emptyDate = "{\"DirEntries\":\"\"}";

        protected void Page_Load(object sender, EventArgs e)
        {
            try
            {
                string path = Request.QueryString["path"];

                if (path != null)
                {
                    StringBuilder response = new StringBuilder();
                    ISVNRepository repository = Global.CurrentRepository;

                    if (repository != null)
                    {
                        // IDictionary<string, string> properties = new Dictionary<string, string>();
                        ICollection<SVNDirEntry> dirEntries =
                            Global.CurrentRepository.GetDir(path, -1, null);

                        SortEntries(dirEntries);

                        response.Append("{ \"DirEntries\" : [");
                        int dirEntryIndex = 0;
                        foreach (SVNDirEntry dirEntry in dirEntries)
                        {
                            response.Append("{ \"type\" : \"").Append(dirEntry.Kind.ToString()).Append("\", ");
                            response.Append("\"label\" : \"").Append(dirEntry.Name).Append("\", ");
                            response.Append("\"path\" : \"").AppendFormat("{0}/{1}", path, dirEntry.RelativePath).Append
                                ("\" }");
                            if (dirEntryIndex < (dirEntries.Count - 1))
                                response.Append(",");
                            dirEntryIndex++;
                        }
                        response.Append("] }");
                    }

                    Response.Write(response);
                }
            }
            catch
            {
                Response.Write(emptyDate);
            }
        }

        private void SortEntries(ICollection<SVNDirEntry> dirEntries)
        {
            List<SVNDirEntry> list = dirEntries as List<SVNDirEntry>;
            if (list == null)
                return;

            list.Sort(CompareBySVNKind);
            int index = 0;
            for (; index < list.Count; index++)
            {
                if (list[index].Kind != SVNNodeKind.dir)
                    break;
            }
            CompareAlphabetically comparer = new CompareAlphabetically();

            list.Sort(0, index, comparer);
            list.Sort(index, list.Count - index, comparer);
        }

        private static int CompareBySVNKind(SVNDirEntry x, SVNDirEntry y)
        {
            if (x == null)
            {
                if (y == null) // If x is null and y is null, they're equal. 
                    return 0;
                else // If x is null and y is not null, y is greater. 
                    return -1;
            }
            else
            {
                // If x is not null and y is null, x is greater.
                if (y == null)
                    return 1;
                else
                {
                    if (x.Kind == y.Kind)
                        return 0;
                    else if (x.Kind == SVNNodeKind.file)
                        return 1;
                    else
                        return -1;
                }
            }
        }


        public class CompareAlphabetically : IComparer<SVNDirEntry>
        {
            public int Compare(SVNDirEntry x, SVNDirEntry y)
            {
                return string.Compare(x.Name, y.Name);
            }
        }
    }
}